package com.lexue.articlesync.service;

import com.lexue.articlesync.adapter.PlatformAdapter;
import com.lexue.articlesync.adapter.PlatformAdapter.PublishResult;
import com.lexue.articlesync.entity.*;
import com.lexue.articlesync.repository.*;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;
import java.util.concurrent.CompletableFuture;

/**
 * 内容同步服务
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class ContentSyncService {
    
    private final PlatformAdapterManager adapterManager;
    private final ArticleRepository articleRepository;
    private final VideoRepository videoRepository;
    private final PublishConfigRepository publishConfigRepository;
    private final PlatformRepository platformRepository;
    private final PlatformAuthRepository authRepository;
    
    /**
     * 同步文章到所有配置的平台
     */
    @Async
    @Transactional
    public CompletableFuture<Void> syncArticle(Long articleId) {
        try {
            Article article = articleRepository.findById(articleId)
                    .orElseThrow(() -> new IllegalArgumentException("文章不存在: " + articleId));
            
            // 更新文章状态为发布中
            article.setStatus(Article.ArticleStatus.PUBLISHING);
            articleRepository.save(article);
            
            // 获取文章的发布配置
            List<PublishConfig> configs = publishConfigRepository.findByArticleId(articleId);
            
            boolean hasSuccess = false;
            boolean hasFailure = false;
            
            for (PublishConfig config : configs) {
                if (!config.getEnabled()) {
                    config.setStatus(PublishConfig.PublishStatus.SKIPPED);
                    publishConfigRepository.save(config);
                    continue;
                }
                
                try {
                    PublishResult result = publishToSinglePlatform(article, config);
                    if (result.isSuccess()) {
                        hasSuccess = true;
                        config.setStatus(PublishConfig.PublishStatus.SUCCESS);
                        config.setPlatformContentId(result.getContentId());
                        config.setPlatformUrl(result.getContentUrl());
                        config.setPublishedAt(LocalDateTime.now());
                    } else {
                        hasFailure = true;
                        config.setStatus(PublishConfig.PublishStatus.FAILED);
                        config.setErrorMessage(result.getErrorMessage());
                        config.incrementRetryCount();
                    }
                } catch (Exception e) {
                    hasFailure = true;
                    config.setStatus(PublishConfig.PublishStatus.FAILED);
                    config.setErrorMessage("发布异常: " + e.getMessage());
                    config.incrementRetryCount();
                    log.error("发布文章到平台失败: {}", config.getPlatform().getName(), e);
                }
                
                publishConfigRepository.save(config);
            }
            
            // 更新文章整体状态
            if (hasSuccess && !hasFailure) {
                article.setStatus(Article.ArticleStatus.PUBLISHED);
            } else if (hasFailure) {
                article.setStatus(Article.ArticleStatus.FAILED);
            }
            
            articleRepository.save(article);
            log.info("文章同步完成: {}", articleId);
            
        } catch (Exception e) {
            log.error("同步文章失败: {}", articleId, e);
        }
        
        return CompletableFuture.completedFuture(null);
    }
    
    /**
     * 同步视频到所有配置的平台
     */
    @Async
    @Transactional
    public CompletableFuture<Void> syncVideo(Long videoId) {
        try {
            Video video = videoRepository.findById(videoId)
                    .orElseThrow(() -> new IllegalArgumentException("视频不存在: " + videoId));
            
            // 更新视频状态为发布中
            video.setStatus(Video.VideoStatus.PUBLISHING);
            videoRepository.save(video);
            
            // 获取视频的发布配置
            List<PublishConfig> configs = publishConfigRepository.findByVideoId(videoId);
            
            boolean hasSuccess = false;
            boolean hasFailure = false;
            
            for (PublishConfig config : configs) {
                if (!config.getEnabled()) {
                    config.setStatus(PublishConfig.PublishStatus.SKIPPED);
                    publishConfigRepository.save(config);
                    continue;
                }
                
                try {
                    PublishResult result = publishVideoToSinglePlatform(video, config);
                    if (result.isSuccess()) {
                        hasSuccess = true;
                        config.setStatus(PublishConfig.PublishStatus.SUCCESS);
                        config.setPlatformContentId(result.getContentId());
                        config.setPlatformUrl(result.getContentUrl());
                        config.setPublishedAt(LocalDateTime.now());
                    } else {
                        hasFailure = true;
                        config.setStatus(PublishConfig.PublishStatus.FAILED);
                        config.setErrorMessage(result.getErrorMessage());
                        config.incrementRetryCount();
                    }
                } catch (Exception e) {
                    hasFailure = true;
                    config.setStatus(PublishConfig.PublishStatus.FAILED);
                    config.setErrorMessage("发布异常: " + e.getMessage());
                    config.incrementRetryCount();
                    log.error("发布视频到平台失败: {}", config.getPlatform().getName(), e);
                }
                
                publishConfigRepository.save(config);
            }
            
            // 更新视频整体状态
            if (hasSuccess && !hasFailure) {
                video.setStatus(Video.VideoStatus.PUBLISHED);
            } else if (hasFailure) {
                video.setStatus(Video.VideoStatus.FAILED);
            }
            
            videoRepository.save(video);
            log.info("视频同步完成: {}", videoId);
            
        } catch (Exception e) {
            log.error("同步视频失败: {}", videoId, e);
        }
        
        return CompletableFuture.completedFuture(null);
    }
    
    /**
     * 发布文章到单个平台
     */
    private PublishResult publishToSinglePlatform(Article article, PublishConfig config) {
        Platform platform = config.getPlatform();
        
        // 获取平台适配器
        PlatformAdapter adapter = adapterManager.getAdapter(platform.getCode());
        
        // 获取平台认证信息
        List<PlatformAuth> authList = authRepository.findByPlatformCode(platform.getCode());
        if (authList.isEmpty()) {
            return new PublishResult(false, "平台认证信息不存在: " + platform.getName());
        }
        
        PlatformAuth auth = authList.get(0); // 使用第一个有效的认证
        
        // 验证认证信息
        if (!adapter.validateAuth(auth)) {
            return new PublishResult(false, "平台认证信息无效: " + platform.getName());
        }
        
        // 构建发布选项
        PlatformAdapter.PublishOptions options = new PlatformAdapter.PublishOptions();
        options.setTitle(config.getPlatformTitle() != null ? config.getPlatformTitle() : article.getTitle());
        options.setContent(config.getPlatformContent() != null ? config.getPlatformContent() : article.getHtmlContent());
        options.setTags(config.getPlatformTags() != null ? config.getPlatformTags() : article.getTags());
        options.setCoverImage(config.getPlatformCover() != null ? config.getPlatformCover() : article.getCoverImage());
        options.setOriginal(article.getIsOriginal());
        options.setJoinActivity(article.getJoinActivity());
        options.setActivityId(article.getActivityId());
        options.setAutoPublish(true);
        
        // 执行发布
        return adapter.publishArticle(article, auth, options);
    }
    
    /**
     * 发布视频到单个平台
     */
    private PublishResult publishVideoToSinglePlatform(Video video, PublishConfig config) {
        Platform platform = config.getPlatform();
        
        // 获取平台适配器
        PlatformAdapter adapter = adapterManager.getAdapter(platform.getCode());
        
        // 获取平台认证信息
        List<PlatformAuth> authList = authRepository.findByPlatformCode(platform.getCode());
        if (authList.isEmpty()) {
            return new PublishResult(false, "平台认证信息不存在: " + platform.getName());
        }
        
        PlatformAuth auth = authList.get(0); // 使用第一个有效的认证
        
        // 验证认证信息
        if (!adapter.validateAuth(auth)) {
            return new PublishResult(false, "平台认证信息无效: " + platform.getName());
        }
        
        // 构建发布选项
        PlatformAdapter.PublishOptions options = new PlatformAdapter.PublishOptions();
        options.setTitle(config.getPlatformTitle() != null ? config.getPlatformTitle() : video.getTitle());
        options.setContent(config.getPlatformContent() != null ? config.getPlatformContent() : video.getDescription());
        options.setTags(config.getPlatformTags() != null ? config.getPlatformTags() : video.getTags());
        options.setCoverImage(config.getPlatformCover() != null ? config.getPlatformCover() : video.getCoverImage());
        options.setOriginal(video.getIsOriginal());
        options.setJoinActivity(video.getJoinActivity());
        options.setActivityId(video.getActivityId());
        options.setAutoPublish(true);
        
        // 执行发布
        return adapter.publishVideo(video, auth, options);
    }
    
    /**
     * 定时任务：处理定时发布的内容
     */
    @Scheduled(fixedDelay = 60000) // 每分钟检查一次
    @Transactional
    public void processScheduledContent() {
        LocalDateTime now = LocalDateTime.now();
        
        // 处理定时发布的文章
        List<Article> scheduledArticles = articleRepository.findScheduledArticles(now);
        for (Article article : scheduledArticles) {
            log.info("开始处理定时发布的文章: {}", article.getId());
            syncArticle(article.getId());
        }
        
        // 处理定时发布的视频
        List<Video> scheduledVideos = videoRepository.findScheduledVideos(now);
        for (Video video : scheduledVideos) {
            log.info("开始处理定时发布的视频: {}", video.getId());
            syncVideo(video.getId());
        }
    }
    
    /**
     * 定时任务：重试失败的发布
     */
    @Scheduled(fixedDelay = 300000) // 每5分钟检查一次
    @Transactional
    public void retryFailedPublish() {
        List<PublishConfig> failedConfigs = publishConfigRepository.findFailedConfigsForRetry();
        
        for (PublishConfig config : failedConfigs) {
            log.info("重试失败的发布配置: {} - {}", 
                    config.getId(), config.getPlatform().getName());
            
            try {
                PublishResult result;
                if (config.getArticle() != null) {
                    result = publishToSinglePlatform(config.getArticle(), config);
                } else if (config.getVideo() != null) {
                    result = publishVideoToSinglePlatform(config.getVideo(), config);
                } else {
                    continue;
                }
                
                if (result.isSuccess()) {
                    config.setStatus(PublishConfig.PublishStatus.SUCCESS);
                    config.setPlatformContentId(result.getContentId());
                    config.setPlatformUrl(result.getContentUrl());
                    config.setPublishedAt(LocalDateTime.now());
                    config.setErrorMessage(null);
                } else {
                    config.incrementRetryCount();
                    config.setErrorMessage(result.getErrorMessage());
                }
                
                publishConfigRepository.save(config);
                
            } catch (Exception e) {
                config.incrementRetryCount();
                config.setErrorMessage("重试异常: " + e.getMessage());
                publishConfigRepository.save(config);
                log.error("重试发布配置失败: {}", config.getId(), e);
            }
        }
    }
    
    /**
     * 创建文章的发布配置
     */
    @Transactional
    public void createArticlePublishConfigs(Article article, List<Long> platformIds) {
        for (Long platformId : platformIds) {
            Platform platform = platformRepository.findById(platformId)
                    .orElseThrow(() -> new IllegalArgumentException("平台不存在: " + platformId));
            
            // 检查平台是否支持文章
            if (!platform.supportsType("article")) {
                log.warn("平台 {} 不支持文章发布", platform.getName());
                continue;
            }
            
            PublishConfig config = PublishConfig.builder()
                    .article(article)
                    .platform(platform)
                    .platformTitle(article.getTitle())
                    .platformContent(article.getHtmlContent())
                    .platformTags(article.getTags())
                    .platformCover(article.getCoverImage())
                    .enabled(true)
                    .status(PublishConfig.PublishStatus.PENDING)
                    .retryCount(0)
                    .maxRetryCount(3)
                    .build();
            
            publishConfigRepository.save(config);
        }
    }
    
    /**
     * 创建视频的发布配置
     */
    @Transactional
    public void createVideoPublishConfigs(Video video, List<Long> platformIds) {
        for (Long platformId : platformIds) {
            Platform platform = platformRepository.findById(platformId)
                    .orElseThrow(() -> new IllegalArgumentException("平台不存在: " + platformId));
            
            // 检查平台是否支持视频
            if (!platform.supportsType("video")) {
                log.warn("平台 {} 不支持视频发布", platform.getName());
                continue;
            }
            
            PublishConfig config = PublishConfig.builder()
                    .video(video)
                    .platform(platform)
                    .platformTitle(video.getTitle())
                    .platformContent(video.getDescription())
                    .platformTags(video.getTags())
                    .platformCover(video.getCoverImage())
                    .enabled(true)
                    .status(PublishConfig.PublishStatus.PENDING)
                    .retryCount(0)
                    .maxRetryCount(3)
                    .build();
            
            publishConfigRepository.save(config);
        }
    }
}